import type { RouteRecordRaw } from 'vue-router'
import { LoadingComponent } from './loadingComponent'
import { useChartResize } from './useChartResize'
import type { ApplicationMenuInfo } from '@/types'
import { TEMP_REG } from '@/constant/modules/template'

/** 默认路径 */
const defGlobPath = import.meta.glob([
  '@/views/**/*.vue',
  '!@/views/**/components/*',
])

/** 根据菜单数据创建路由 */
export function createRouters(menu: ApplicationMenuInfo[]) {
  /** 全屏层级 */
  const fullscreenLevel: RouteRecordRaw[] = []
  /** 驾驶舱层级 */
  const cockpitRawLevel: ApplicationMenuInfo[] = []
  const handler = (menu: ApplicationMenuInfo[]): RouteRecordRaw[] => {
    return menu.reduce((pre: RouteRecordRaw[], cur: ApplicationMenuInfo) => {
      const children: RouteRecordRaw[] = []
      const meta = {
        title: cur.menuName,
        power: cur.power,
        type: cur.menuType,
      }

      let redirect = ''
      let path = cur.menuAddress
      if (cur.children && cur.children.length > 0) {
        children.push(...handler(cur.children))
        redirect = children[0]?.path ?? '/'
        !path && (path = `${redirect}_${uuid()}`)
      }

      const componentPath = cur.identifying
        ? `/${cur.identifying}/${cur.identifying}.vue`
        : `/src/views${cur.menuAddress}/index.vue`

      const getTemplate = (address: string) => {
        if (TEMP_REG.test(address)) {
          return address.replace(TEMP_REG, (_, m) => {
            return `/src/views/${m}/index.vue`
          })
        }
        return ''
      }

      const template = getTemplate(cur.menuAddress ?? '')
      let component: RouteRecordRaw['component'] = null
      for (const key in defGlobPath) {
        if (key.includes(componentPath) || key === template) {
          component = createCustomComponent(path, defGlobPath[key])
          break
        }
      }

      const router = {
        meta,
        path,
        name: cur.identifying ?? cur.menuName,
        children,
        ...(() => children && children.length > 0 && { redirect })(),
        component,
      } as RouteRecordRaw
      // ? 驾驶舱
      if (cur.menuType === 4) {
        cockpitRawLevel.push(cur)
        fullscreenLevel.push(router)
        return [...pre]
      }
      // ? 全屏层级抽离
      if (cur.isFullscreen) {
        fullscreenLevel.push(router)
        return [...pre]
      }
      return [...pre, router]
    }, [] as RouteRecordRaw[])
  }

  const layoutLevel = generateLayoutLevel(handler(menu))
  const routes = [layoutLevel, ...fullscreenLevel]

  return routes
}

function generateLayoutLevel(router: RouteRecordRaw[]) {
  const layoutLevel: RouteRecordRaw = {
    name: '布局',
    path: '/layout',
    component: () => import('@/layout/index.vue'),
    redirect: '/home',
    children: router,
  }

  return layoutLevel
}

/** 将指定组件设置自定义名称 */
export default function createCustomComponent(
  customName: string,
  asyncComponent: any,
) {
  return defineComponent({
    name: customName,
    setup() {
      useChartResize(customName)
      const router = useRouter()
      const { isRefresh } = storeToRefs(useGlobalStore())
      const com = defineAsyncComponent({
        loader: asyncComponent as any,
        loadingComponent: h(LoadingComponent, {
          fullscreen: customName.includes('cockpit'),
        }),
      })

      /**
       * ! 当前显示页面是否为路径对于页面
       * ! 不加该条件每次刷新将会刷新所有缓存页面
       */
      const isCurrent = computed(
        () => router.currentRoute.value.path === customName,
      )
      return () => {
        return isRefresh.value && isCurrent.value ? h('div') : h(com)
      }
    },
  })
}
